﻿namespace NetworkChangeDetector
{
    using System;
    using System.ComponentModel;
    using System.Net.NetworkInformation;
    using Microsoft.Phone.Net.NetworkInformation;

    public class NetworkEventArgs : EventArgs
    {
        public NetworkEventArgs(string msg)
        {
            Message = msg;
        }

        public string Message { get; set; }
    }

    public class ZuneDetector
    {
        private static readonly ZuneDetector _instance = new ZuneDetector();
        private BackgroundWorker _networkWorker;

        public event EventHandler<NetworkEventArgs> OnZuneConnected;
        public event EventHandler<NetworkEventArgs> OnZuneDisconnected;

        private bool _isZuneConnected;

        public bool IsZuneConnected
        {
            get { return _isZuneConnected; }
            set { _isZuneConnected = value; }
        }

        public ZuneDetector()
        {
            _networkWorker = new BackgroundWorker();
            _networkWorker.RunWorkerCompleted += new RunWorkerCompletedEventHandler(networkWorker_RunWorkerCompleted);
            _networkWorker.DoWork += new DoWorkEventHandler(networkWorker_DoWork);

            //NetworkChange.NetworkAddressChanged += NetworkChanged;
            DeviceNetworkInformation.NetworkAvailabilityChanged += new EventHandler<NetworkNotificationEventArgs>(NetworkChanged);
        }

        public static ZuneDetector Instance
        {
            get
            {
                return _instance;
            }
        }

        public bool CheckZuneConnection()
        {
            bool result = false;
            NetworkInterfaceList networkInterfaceList = new NetworkInterfaceList();
            foreach (NetworkInterfaceInfo ni in networkInterfaceList)
            {
                if (_isZuneConnetion(ni))
                {
                    result = true;
                    break;
                }
            }

            IsZuneConnected = result;
            return result;
        }

        public void AsyncCheckZuneConnection()
        {
            if (!_networkWorker.IsBusy)
            {
                _networkWorker.RunWorkerAsync();
            }
        }

        private void networkWorker_DoWork(object sender, DoWorkEventArgs e)
        {
            CheckZuneConnection();
        }

        private void networkWorker_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
        {
        }

        private bool _isZuneConnetion(NetworkInterfaceInfo ni)
        {
            if (ni.InterfaceType == NetworkInterfaceType.Ethernet
                   && !ni.InterfaceName.Contains("Loopback"))
            {
                return true;
            }
            else
                return false;
        }

        private void NetworkChanged(object sender, NetworkNotificationEventArgs e)
        {
            string msg = DateTime.Now.ToString() + ", ";
            switch (e.NotificationType)
            {
                case NetworkNotificationType.InterfaceConnected:
                    msg += "Connected to " + e.NetworkInterface.InterfaceName;
                    if (_isZuneConnetion(e.NetworkInterface))
                    {
                        IsZuneConnected = true;
                        Notify(OnZuneConnected, new NetworkEventArgs(msg));
                    }
                    break;
                case NetworkNotificationType.InterfaceDisconnected:
                    msg += "Disconnected from " + e.NetworkInterface.InterfaceName;
                    if (_isZuneConnetion(e.NetworkInterface))
                    {
                        IsZuneConnected = false;
                        Notify(OnZuneDisconnected, new NetworkEventArgs(msg));
                    }
                    break;
                case NetworkNotificationType.CharacteristicUpdate:
                    msg += "Characteristics changed for " + e.NetworkInterface.InterfaceName;
                    break;
                default:
                    msg += "Unknown change with " + e.NetworkInterface.InterfaceName;
                    break;
            }
        }

        protected void Notify(EventHandler<NetworkEventArgs> handler, NetworkEventArgs e)
        {
            if (handler != null)
            {
                handler(this, e);
            }
        }
    }
}